package com.jichaoyun.service.impl;

import com.alibaba.druid.support.json.JSONUtils;
import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.util.MapUtils;
import com.alibaba.excel.write.style.HorizontalCellStyleStrategy;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.jichaoyun.common.model.FileInfo;
import com.jichaoyun.common.model.PagedResult;
import com.jichaoyun.common.utils.ExcelStyleUtils;
import com.jichaoyun.common.utils.FileUtil;
import com.jichaoyun.dao.mapper.InspectPictureMapper;
import com.jichaoyun.dao.mapper.SignaturePictureMapper;
import com.jichaoyun.dao.mapper.StationInspectionMapper;
import com.jichaoyun.model.entity.InspectPicture;
import com.jichaoyun.model.entity.SignaturePicture;
import com.jichaoyun.model.entity.StationInfo;
import com.jichaoyun.model.entity.StationInspection;
import com.jichaoyun.common.enums.MyExceptiontType;
import com.jichaoyun.common.ex.MyException;
import com.jichaoyun.model.vo.InspectVo;
import com.jichaoyun.model.vo.StationInspectionVo;
import com.jichaoyun.service.IStationInfoService;
import com.jichaoyun.service.StationInspectionService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.net.URLEncoder;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.format.DateTimeFormatter;
import java.time.format.DateTimeParseException;
import java.util.*;

/**
* @author ljc
* @description 针对表【station_inspection】的数据库操作Service实现
* @createDate 2023-12-09 13:42:05
*/
@Service
public class StationInspectionServiceImpl extends ServiceImpl<StationInspectionMapper, StationInspection>
    implements StationInspectionService{

    @Value("${web.inspect-path}")
    private String uploadPath;

    @Autowired
    private StationInspectionMapper stationInspectionMapper;

    @Autowired
    private InspectPictureMapper inspectPictureMapper;

    @Autowired
    private SignaturePictureMapper signaturePictureMapper;

    @Autowired
    private IStationInfoService stationInfoService;


    @Override
    public String insertSignatureInspectPhoto(Integer num,MultipartFile photo) {
        LambdaQueryWrapper<StationInspection> delwp = new LambdaQueryWrapper<>();
        delwp.eq(StationInspection::getInspectId,num);

        String newFileFoader = uploadPath + "/" + num.toString() + "/" + "Signature";
        //上传图片
        FileUtil util1 = new FileUtil();
        FileInfo info1 = util1.upload(photo, newFileFoader);
        if (info1==null){
            stationInspectionMapper.delete(delwp);
            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD2,null);
        }
        if(photo.getSize() > 20*1024*1024){
            stationInspectionMapper.delete(delwp);
            util1.deleteFile(info1.getSavePath());
            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD1,null);
        }else if(!(info1.getSuffix().equals(".jpg")||info1.getSuffix().equals(".png")
                ||info1.getSuffix().equals(".JPG")||info1.getSuffix().equals(".PNG")
                ||info1.getSuffix().equals(".jpeg")||info1.getSuffix().equals(".JPEG"))){
            stationInspectionMapper.delete(delwp);
            util1.deleteFile(info1.getSavePath());
            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD3,null);
        }else{
            SignaturePicture signaturePicture = new SignaturePicture();
            signaturePicture.setInspectId(num);
            signaturePicture.setSignaturePicture(info1.getFileName());
            signaturePictureMapper.insert(signaturePicture);
        }
        return null;
    }


    @Override
    public String insertInspectPhoto(Integer num, MultipartFile photo) {
        LambdaQueryWrapper<StationInspection> delwp = new LambdaQueryWrapper<>();
        delwp.eq(StationInspection::getInspectId,num);

        String newFileFoader = uploadPath + "/" + num.toString() + "/" + "Inspect";
        //上传故障图片
        FileUtil util1 = new FileUtil();
        FileInfo info1 = util1.upload(photo, newFileFoader);
        if (info1==null){
            stationInspectionMapper.delete(delwp);
            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD2,null);
        }
        if(photo.getSize() > 20*1024*1024){
            stationInspectionMapper.delete(delwp);
            util1.deleteFile(info1.getSavePath());
            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD1,null);
        }else if(!(info1.getSuffix().equals(".jpg")||info1.getSuffix().equals(".png")
                ||info1.getSuffix().equals(".JPG")||info1.getSuffix().equals(".PNG")
                ||info1.getSuffix().equals(".jpeg")||info1.getSuffix().equals(".JPEG"))){
            stationInspectionMapper.delete(delwp);
            util1.deleteFile(info1.getSavePath());
            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD3,null);
        }else{
            InspectPicture inspectPicture = new InspectPicture();
            inspectPicture.setInspectId(num);
            inspectPicture.setInspectPicture(info1.getFileName());
            inspectPictureMapper.insert(inspectPicture);
        }

        return null;
    }


    @Override
    public Integer insertInspectInfo(InspectVo inspectVo) {

        StationInspection stationInspection = new StationInspection();
        BeanUtils.copyProperties(inspectVo,stationInspection);

        try {
            // 将字符串转换为LocalTime
            DateTimeFormatter formatter0 = DateTimeFormatter.ofPattern("HH:mm:ss");
            LocalTime localTime = LocalTime.parse(inspectVo.getStartTime(), formatter0);
            stationInspection.setStartTime(localTime);
        } catch (DateTimeParseException e) {
            // 处理解析异常
            System.err.println("无法将字符串转换为LocalTime: " + e.getMessage());
        }
        //生成num的号码编号
        LambdaQueryWrapper<StationInspection> wp = new LambdaQueryWrapper<>();
        wp.eq(StationInspection::getInspectDate,inspectVo.getInspectDate());
        Long count = stationInspectionMapper.selectCount(wp);
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyyMMdd");
        LocalDateTime now = LocalDateTime.now();
        int year = now.getYear();
        int month = now.getMonthValue();
        int day = now.getDayOfMonth();
        Integer num = year%100*10000000+month*100000+day*1000+count.intValue();
        stationInspection.setInspectId(num);
        String newFileFoader = uploadPath + "/" + num.toString();
        String newFileFoader0 = uploadPath + "/" + num.toString()+ "/" + "Signature";
        String newFileFoader1 = uploadPath + "/" + num.toString()+ "/" + "Inspect";
        File directory = new File(newFileFoader);
        File directory0 = new File(newFileFoader0);
        File directory1 = new File(newFileFoader1);
        // 检查目录是否存在，如果不存在则创建
        if (!directory.exists()) {
            try {
                // 使用mkdirs()方法创建目录，可以创建多级目录
                boolean isCreated = directory.mkdirs();
                boolean isCreated0 = directory0.mkdirs();
                boolean isCreated1 = directory1.mkdirs();
                if (isCreated && isCreated0 && isCreated1) {
                    System.out.println("目录创建成功: " + newFileFoader);
                    System.out.println("目录创建成功: " + newFileFoader0);
                    System.out.println("目录创建成功: " + newFileFoader1);
                } else {
                    System.out.println("目录创建失败");
                }
            } catch (SecurityException se) {
                // 处理安全异常，比如没有足够的权限
                System.err.println("创建目录时出现安全异常：" + se.getMessage());
            }
        } else {
            System.out.println("目录已存在: " + newFileFoader);
        }

        String filePath = newFileFoader+ "/"+ num.toString() +".txt";

        try {
            // 创建File对象
            File file = new File(filePath);

            // 检查文件是否存在，如果不存在则创建
            if (!file.exists()) {
                // 使用createNewFile()方法创建文件
                boolean isCreated = file.createNewFile();

                if (isCreated) {
                    System.out.println("文件创建成功: " + filePath);

                    // 使用FileWriter写入文本内容
                    try (FileWriter writer = new FileWriter(file)) {
                        for (String line : inspectVo.getRouteList()) {
                            writer.write(line);
                            writer.write("\n");
                        }
                        stationInspection.setRoute(filePath);
                    } catch (IOException e) {
                        System.err.println("写入文件时发生错误: " + e.getMessage());
                    }
                } else {
                    System.out.println("文件创建失败");
                }
            } else {
                System.out.println("文件已存在: " + filePath);
            }
        } catch (IOException e) {
            // 处理IO异常，比如没有足够的权限或者磁盘空间不足
            System.err.println("创建文件时出现IO异常：" + e.getMessage());
        }
        stationInspectionMapper.insert(stationInspection);
//        //上传签名图片
//        FileUtil util = new FileUtil();
//        MultipartFile file = inspectVo.getSignature();
//        if(file == null){
//            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD0,null);
//        }
//        FileInfo info = util.upload(file, newFileFoader);
//        if (info==null){
//            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD2,null);
//        }
//        if(file.getSize() > 20*1024*1024){
//            util.deleteFile(info.getSavePath());
//            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD1,null);
//        }else if(!(info.getSuffix().equals(".jpg")||info.getSuffix().equals(".png")
//                ||info.getSuffix().equals(".JPG")||info.getSuffix().equals(".PNG")
//                ||info.getSuffix().equals(".jpeg")||info.getSuffix().equals(".JPEG"))){
//            util.deleteFile(info.getSavePath());
//            throw new MyException(MyExceptiontType.IMAGEUPLOADFAILD3,null);
//        }else{
//            stationInspection.setSignaturePicture(info.getFileName());
//            stationInspectionMapper.insert(stationInspection);
//        }
        return num;
    }

   // 巡检逻辑改造：和宁波一致
//    /**
//     * 根据日期返回巡检记录
//     * @param date
//     * @return
//     */
//    @Override
//    public PagedResult getStationInspectionInfo(LocalDate date,Integer pageNo,Integer pageSize) {
//
//        List<Object> list = new ArrayList<>();
//        LocalDateTime day_start = LocalDateTime.of(date, LocalTime.MIN);
//
//        IPage<StationInfo> infoIPage = stationInfoService.getStationInfoByXunjian(pageNo,pageSize);
//        List<StationInfo> stationInfos = infoIPage.getRecords();
//        PagedResult pagedResult = new PagedResult();
//        pagedResult.setTotal((int) infoIPage.getTotal());
//        pagedResult.setPages((int) infoIPage.getPages());
//
//        for(StationInfo item: stationInfos){
//            LambdaQueryWrapper<StationInspection> wrapper = new LambdaQueryWrapper<>();
//            wrapper.gt(StationInspection::getStartTime,day_start)
//                    .le(StationInspection::getStartTime,day_start.plusDays(1))
//                    .eq(StationInspection::getStationNo,item.getStationNo());
//            List<StationInspection> resList = this.stationInspectionMapper.selectList(wrapper);
//
//            Map<String,List<Object>> resMap = new HashMap<>();
//            List<Object> res = new ArrayList<>();
//
//            for(StationInspection item1 : resList){
//               res.add(item1.getInspectTime().toString());
//            }
//            resMap.put(item.getStationName(),res);
//            list.add(resMap);
//        }
//
//        pagedResult.setRows(list);
//
//        return pagedResult;
//    }

    @Override
    public List<StationInspectionVo> getAllStationInspection() {
//        LambdaQueryWrapper<StationInspection> lambdaQueryWrapper = new LambdaQueryWrapper<>();
//        lambdaQueryWrapper.orderByAsc(StationInspection::getStationNo);
        List<StationInspectionVo> resList = this.stationInspectionMapper.selectExcelList1();

        return resList;
    }

    @Override
    public List<StationInspectionVo> getAllStationInspection(LocalDate dateTime) {
//        LambdaQueryWrapper<StationInspection> lambdaQueryWrapper = new LambdaQueryWrapper<>();
//        lambdaQueryWrapper.between(StationInspection::getInspectTime,dateTime,dateTime.plusDays(1))
//                .orderByAsc(StationInspection::getStationNo);
        List<StationInspectionVo> resList = this.stationInspectionMapper.selectExcelList(dateTime,dateTime.plusDays(1));

        return resList;
    }

    // 巡检逻辑改造：和宁波一致   查询
    @Override
    public List<InspectVo> getInspectInfo(String date, String type) {
        LambdaQueryWrapper<StationInspection> lambdaQueryWrapper = new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(StationInspection::getInspectDate,date)
                .eq(StationInspection::getInspectType,type);
        List<StationInspection> stationInspectionList = this.stationInspectionMapper.selectList(lambdaQueryWrapper);

        List<InspectVo> res = new ArrayList<>();
        for(StationInspection item : stationInspectionList){
            InspectVo inspectVo = new InspectVo();
            BeanUtils.copyProperties(item,inspectVo);
            LambdaQueryWrapper<InspectPicture> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(InspectPicture::getInspectId,item.getInspectId());
            List<InspectPicture> inspectPictures = this.inspectPictureMapper.selectList(queryWrapper);
            List<String> nameList = new ArrayList<>();
            for(InspectPicture inspectPicture:inspectPictures){
                nameList.add(inspectPicture.getInspectPicture());
            }
            inspectVo.setFileNames(nameList);

            LambdaQueryWrapper<SignaturePicture> queryWrapper0 = new LambdaQueryWrapper<>();
            queryWrapper0.eq(SignaturePicture::getInspectId,item.getInspectId());
            List<SignaturePicture> signaturePictures = this.signaturePictureMapper.selectList(queryWrapper0);
            List<String> nameList0 = new ArrayList<>();
            for(SignaturePicture signaturePicture:signaturePictures){
                nameList0.add(signaturePicture.getSignaturePicture());
            }
            inspectVo.setSignatureNames(nameList0);

            if(item.getStartTime()!=null){
                inspectVo.setStartTime(item.getStartTime().toString());
            }else {
                inspectVo.setStartTime(null);
            }

            if(item.getRoute() != null){
                List<String> lines = new ArrayList<>();
                File file = new File(item.getRoute());

                try (BufferedReader reader = new BufferedReader(new FileReader(file))) {
                    String line;
                    while ((line = reader.readLine()) != null) {
                        lines.add(line);
                    }
                } catch (IOException e) {
                    System.err.println("读取文件时发生错误: " + e.getMessage());
                }
                inspectVo.setRouteList(lines);
            }
            res.add(inspectVo);
        }
        return res;
    }

    // 巡检逻辑改造：和宁波一致   待改造
    /**
     * 某日巡检信息导出到excel
     * @param date
     * @param response
     * @throws IOException
     */
    @Override
    public void getStationInspectionExcel(String date, HttpServletResponse response) throws IOException {
        // 定义日期格式
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
        // 将字符串转换为 LocalDate
        LocalDate theDate = LocalDate.parse(date, formatter);

        List<StationInspectionVo> resList = getAllStationInspection(theDate);

        // 创建 DateTimeFormatter 对象，定义日期格式
        DateTimeFormatter formatter1 = DateTimeFormatter.ofPattern("yyyy年M月d日 ");
        // 使用 DateTimeFormatter 格式化 LocalDateTime 对象
        String formattedDate = theDate.format(formatter1);

        try {
            response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
            response.setCharacterEncoding("utf-8");
            // 这里URLEncoder.encode可以防止中文乱码 当然和easyexcel没有关系
            String fileName = URLEncoder.encode(formattedDate + "巡检信息表", "UTF-8").replaceAll("\\+", "%20");
            response.setHeader("Content-disposition", "attachment;filename*=utf-8''" + fileName + ".xlsx");
            HorizontalCellStyleStrategy horizontalCellStyleStrategy = new HorizontalCellStyleStrategy(ExcelStyleUtils.getHeadStyle(), ExcelStyleUtils.getContentStyle());

            // 这里需要设置不关闭流
            EasyExcel.write(response.getOutputStream(), StationInspectionVo.class)
                    .registerWriteHandler(horizontalCellStyleStrategy)
                    .autoCloseStream(Boolean.FALSE)
                    .sheet("sheet1")
                    .doWrite(resList);

        } catch (Exception e) {
            // 重置response
            response.reset();
            response.setContentType("application/json");
            response.setCharacterEncoding("utf-8");
            Map<String, String> map = MapUtils.newHashMap();
            map.put("status", "failure");

            map.put("message", "下载文件失败" + e.getMessage());
            response.getWriter().println(JSONUtils.toJSONString(map));
            throw new MyException(MyExceptiontType.FILEDOWNLOADFAIL,"下载文件失败");
        }
    }


    // 巡检逻辑改造：和宁波一致   待改造
    /**
     * 历史巡检信息导出到excel
     * @param response
     * @throws IOException
     */
    @Override
    public void getStationInspectionExcel(HttpServletResponse response) throws IOException {

        List<StationInspectionVo> resList = getAllStationInspection();

        try {
            response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
            response.setCharacterEncoding("utf-8");
            // 这里URLEncoder.encode可以防止中文乱码 当然和easyexcel没有关系
            String fileName = URLEncoder.encode("历史巡检信息表", "UTF-8").replaceAll("\\+", "%20");
            response.setHeader("Content-disposition", "attachment;filename*=utf-8''" + fileName + ".xlsx");
            HorizontalCellStyleStrategy horizontalCellStyleStrategy = new HorizontalCellStyleStrategy(ExcelStyleUtils.getHeadStyle(), ExcelStyleUtils.getContentStyle());

            // 这里需要设置不关闭流
            EasyExcel.write(response.getOutputStream(), StationInspectionVo.class)
                    .registerWriteHandler(horizontalCellStyleStrategy)
                    .autoCloseStream(Boolean.FALSE)
                    .sheet("sheet1")
                    .doWrite(resList);

        } catch (Exception e) {
            // 重置response
            response.reset();
            response.setContentType("application/json");
            response.setCharacterEncoding("utf-8");
            Map<String, String> map = MapUtils.newHashMap();
            map.put("status", "failure");

            map.put("message", "下载文件失败" + e.getMessage());
            response.getWriter().println(JSONUtils.toJSONString(map));
            throw new MyException(MyExceptiontType.FILEDOWNLOADFAIL,"下载文件失败");
        }
    }
}




